using System;
using Needle.Utils.Collections;

namespace Needle.Utils.Parser
{/// <summary></summary>
    public class Keyword
    {/// <summary></summary>
        public Keyword(string keyword, KeywordType type)
        {
            _Value = keyword;
            _type = type;
        }

        private String _Value;
        /// <summary></summary>
        public String Value
        { get { return _Value; } }

        private KeywordType _type;
        /// <summary></summary>
        public KeywordType Type
        {
            get { return _type; }
        }
        /// <summary></summary>
        public static KeywordCollection Get()
        {
            KeywordCollection keywords = new KeywordCollection();

            // references
            keywords.Add(new Keyword("base", KeywordType.Normal));
            keywords.Add(new Keyword("this", KeywordType.Normal));

            // exception handling
            keywords.Add(new Keyword("try", KeywordType.Normal));
            keywords.Add(new Keyword("throw", KeywordType.Normal));
            keywords.Add(new Keyword("catch", KeywordType.Normal));
            keywords.Add(new Keyword("finally", KeywordType.Normal));

            // operators
            keywords.Add(new Keyword("as", KeywordType.Normal));
            keywords.Add(new Keyword("is", KeywordType.Normal));
            keywords.Add(new Keyword("new", KeywordType.Normal));
            keywords.Add(new Keyword("lock", KeywordType.Normal));
            keywords.Add(new Keyword("using", KeywordType.Normal));
            keywords.Add(new Keyword("sizeof", KeywordType.Normal));

            // compiler directives
            keywords.Add(new Keyword("fixed", KeywordType.Normal));
            keywords.Add(new Keyword("unsafe", KeywordType.Normal));
            keywords.Add(new Keyword("extern", KeywordType.Normal));
            keywords.Add(new Keyword("checked", KeywordType.Normal));
            keywords.Add(new Keyword("volatile", KeywordType.Normal));
            keywords.Add(new Keyword("unchecked", KeywordType.Normal));
            keywords.Add(new Keyword("stackalloc", KeywordType.Normal));

            // type/member/parameter modifiers
            keywords.Add(new Keyword("ref", KeywordType.Normal));
            keywords.Add(new Keyword("out", KeywordType.Normal));
            keywords.Add(new Keyword("const", KeywordType.Normal));
            keywords.Add(new Keyword("static", KeywordType.Normal));
            keywords.Add(new Keyword("public", KeywordType.Normal));
            keywords.Add(new Keyword("params", KeywordType.Normal));
            keywords.Add(new Keyword("typeof", KeywordType.Normal));
            keywords.Add(new Keyword("sealed", KeywordType.Normal));
            keywords.Add(new Keyword("private", KeywordType.Normal));
            keywords.Add(new Keyword("virtual", KeywordType.Normal));
            keywords.Add(new Keyword("abstract", KeywordType.Normal));
            keywords.Add(new Keyword("override", KeywordType.Normal));
            keywords.Add(new Keyword("explicit", KeywordType.Normal));
            keywords.Add(new Keyword("implicit", KeywordType.Normal));
            keywords.Add(new Keyword("internal", KeywordType.Normal));
            keywords.Add(new Keyword("readonly", KeywordType.Normal));
            keywords.Add(new Keyword("protected", KeywordType.Normal));

            // constants
            keywords.Add(new Keyword("null", KeywordType.Normal));
            keywords.Add(new Keyword("true", KeywordType.Normal));
            keywords.Add(new Keyword("false", KeywordType.Normal));
            keywords.Add(new Keyword("default", KeywordType.Normal));

            // flow control
            keywords.Add(new Keyword("if", KeywordType.Normal));
            keywords.Add(new Keyword("in", KeywordType.Normal));
            keywords.Add(new Keyword("do", KeywordType.Normal));
            keywords.Add(new Keyword("for", KeywordType.Normal));
            keywords.Add(new Keyword("else", KeywordType.Normal));
            keywords.Add(new Keyword("goto", KeywordType.Normal));
            keywords.Add(new Keyword("case", KeywordType.Normal));
            keywords.Add(new Keyword("while", KeywordType.Normal));
            keywords.Add(new Keyword("break", KeywordType.Normal));
            keywords.Add(new Keyword("return", KeywordType.Normal));
            keywords.Add(new Keyword("switch", KeywordType.Normal));
            keywords.Add(new Keyword("foreach", KeywordType.Normal));
            keywords.Add(new Keyword("continue", KeywordType.Normal));

            // type/member declaration
            keywords.Add(new Keyword("enum", KeywordType.Normal));
            keywords.Add(new Keyword("class", KeywordType.Normal));
            keywords.Add(new Keyword("event", KeywordType.Normal));
            keywords.Add(new Keyword("struct", KeywordType.Normal));
            keywords.Add(new Keyword("operator", KeywordType.Normal));
            keywords.Add(new Keyword("delegate", KeywordType.Normal));
            keywords.Add(new Keyword("namespace", KeywordType.Normal));
            keywords.Add(new Keyword("interface", KeywordType.Normal));

            // primitive types
            keywords.Add(new Keyword("int", KeywordType.Normal));
            keywords.Add(new Keyword("bool", KeywordType.Normal));
            keywords.Add(new Keyword("byte", KeywordType.Normal));
            keywords.Add(new Keyword("char", KeywordType.Normal));
            keywords.Add(new Keyword("uint", KeywordType.Normal));
            keywords.Add(new Keyword("void", KeywordType.Normal));
            keywords.Add(new Keyword("long", KeywordType.Normal));
            keywords.Add(new Keyword("float", KeywordType.Normal));
            keywords.Add(new Keyword("sbyte", KeywordType.Normal));
            keywords.Add(new Keyword("short", KeywordType.Normal));
            keywords.Add(new Keyword("ulong", KeywordType.Normal));
            keywords.Add(new Keyword("object", KeywordType.Normal));
            keywords.Add(new Keyword("double", KeywordType.Normal));
            keywords.Add(new Keyword("string", KeywordType.Normal));
            keywords.Add(new Keyword("ushort", KeywordType.Normal));
            keywords.Add(new Keyword("decimal", KeywordType.Normal));

            // contextual
            keywords.Add(new Keyword("get", KeywordType.Contextual));
            keywords.Add(new Keyword("set", KeywordType.Contextual));
            keywords.Add(new Keyword("let", KeywordType.Contextual));
            keywords.Add(new Keyword("from", KeywordType.Contextual));
            keywords.Add(new Keyword("into", KeywordType.Contextual));
            keywords.Add(new Keyword("join", KeywordType.Contextual));
            keywords.Add(new Keyword("group", KeywordType.Contextual));
            keywords.Add(new Keyword("value", KeywordType.Contextual));
            keywords.Add(new Keyword("where", KeywordType.Contextual));
            keywords.Add(new Keyword("yield", KeywordType.Contextual));
            keywords.Add(new Keyword("select", KeywordType.Contextual));
            keywords.Add(new Keyword("orderby", KeywordType.Contextual));
            keywords.Add(new Keyword("partial", KeywordType.Contextual));

            return keywords;
        }
    }
    /// <summary></summary>
    public class KeywordCollection : KeyedCollection<string, Keyword>
    {
        /// <summary></summary>
        public KeywordCollection()
            : base(x => x.Value)
        { }

    }
}

